package com.mj.controller;

import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.mj.domain.ActionBean;
import com.mj.domain.ClassificationBean;
import com.mj.domain.GraphBean;
import com.mj.domain.RuleBean;
import com.mj.repository.GraphObject;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.env.Environment;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;
import com.mj.service.DataAccessService;

import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.*;

/**
 * Created by SXY on 2015/12/8.
 */
@Controller
public class ChartController {

    @Autowired
    private DataAccessService dataAccesser;

    private final static Log logger = LogFactory.getLog(ChartController.class);
    @Autowired
    private Environment env;

    @RequestMapping("/chart.shtml")
    public String chart(Model model) {
        List<GraphBean> graphBeanList = new ArrayList<GraphBean>();
        Map<String, List<ActionBean>> actionMap = new HashMap<String, List<ActionBean>>();

        List<ActionBean> actionBeanList = dataAccesser.getAllActions();
        List<ClassificationBean> classiBeanList = dataAccesser.getAllClassification();

        for (ClassificationBean bean : classiBeanList) {
            List<ActionBean> tempList = new ArrayList<ActionBean>();
            actionMap.put(bean.getClassification_name(), tempList);
        }
        for (ActionBean bean : actionBeanList) {
//            添加到分类中
            String classification = bean.getClassification_name();
            actionMap.get(classification).add(bean);

            GraphBean graphBean = getGraphBean(bean);
            graphBeanList.add(graphBean);
        }

        model.addAttribute("beanList", graphBeanList);
        model.addAttribute("actionMap", actionMap);
        model.addAttribute("classList", classiBeanList);
        model.addAttribute("baseUrl", env.getProperty("base.url"));
        logger.info("****** Chart-Controller ******");
        return "chart";
    }

    /**
     * 获取同类别下的图表 并返回
     * @param request
     * @param model
     * @return
     * @throws UnsupportedEncodingException
     */
    @RequestMapping("/group_action.shtml")
    public String group_action(HttpServletRequest request, Model model) throws UnsupportedEncodingException {
        List<GraphBean> graphBeanList = new ArrayList<GraphBean>();

        List<ActionBean> actionBeanList = dataAccesser.getGroupActions(Integer.parseInt(request.getParameter("name")));

        for (ActionBean bean : actionBeanList) {
            GraphBean graphBean = getGraphBean(bean);
            graphBeanList.add(graphBean);
        }

        model.addAttribute("beanList", graphBeanList);
        logger.info("[------Controller------]: group_action");
        return "actionWidget";
    }

    /**
     * 根据图表id，获取单个图表
     * @param request
     * @param model
     * @return
     */
    @RequestMapping("/action.shtml")
    public String action(HttpServletRequest request, Model model) {
        List<GraphBean> graphBeanList = new ArrayList<GraphBean>();

        ActionBean actionBean = dataAccesser.getOneAction(Integer.parseInt(request.getParameter("id")));

        GraphBean graphBean = getGraphBean(actionBean);
        graphBeanList.add(graphBean);

        model.addAttribute("beanList", graphBeanList);
        logger.info("[------Controller------]: Action");

        return "actionWidget";
    }

    /**
     * 添加类别
     * @param request
     * @return
     * @throws UnsupportedEncodingException
     */
    @RequestMapping(value = "/addClassification.shtml", method = RequestMethod.GET)
    public
    @ResponseBody
    String addClassification(HttpServletRequest request) throws UnsupportedEncodingException {
        request.setCharacterEncoding("UTF-8");
        ClassificationBean classificationBean = new ClassificationBean();

        classificationBean.setClassification_name(request.getParameter("classification_name"));

        dataAccesser.setOneClassification(classificationBean);
        logger.info("[------Controller------]: AddClassification Complete");
        return "success";
    }

    /**
     * 跳转到创建页面 并加载类别信息
     * @param model
     * @return
     */
    @RequestMapping("/toCreateGraph.shtml")
    public String toCreateGraph(Model model) {

        List<ClassificationBean> classList = dataAccesser.getAllClassification();

        model.addAttribute("classList", classList);
        logger.info("[------Controller------]   : toCreateGraph");
        return "createGraph";
    }

    /**
     * 创建一个图表的相关信息，成功后跳转到主页面
     * @param request
     * @param model
     * @return
     */
    @RequestMapping(value = "/createGraph.shtml", method = RequestMethod.POST)
    public String createGraph(HttpServletRequest request, Model model) {

        List beanList = getActionAndRuleBean(request);

        ActionBean actionBean = (ActionBean) beanList.get(0);
        RuleBean ruleBean = (RuleBean) beanList.get(1);

        dataAccesser.creatOneGraph(actionBean, ruleBean);
        return "redirect:/chart.shtml";
    }

    /**
     * 更新数据，成功后重定向
     *
     * @param request
     * @param model
     * @return
     */
    @RequestMapping(value = "/updateGraph.shtml", method = RequestMethod.POST)
    public String updateGraph(HttpServletRequest request, Model model) {
        List beanList = getActionAndRuleBean(request);

        ActionBean actionBean = (ActionBean) beanList.get(0);
        RuleBean ruleBean = (RuleBean) beanList.get(1);

        List<Integer> ruleIdList = dataAccesser.getRuleIdsByActionId(ruleBean.getAction_id());
        ruleBean.setRule_id(ruleIdList.get(0));
        dataAccesser.updateOneGraph(actionBean, ruleBean);

        return "redirect:/chart.shtml";
    }

    /**
     * 跳转到更新界面，并加载数据
     *
     * @param request
     * @param model
     * @return
     */
    @RequestMapping("/toUpdate.shtml")
    public String toUpdate(HttpServletRequest request, Model model) {
        int actionId = Integer.parseInt(request.getParameter("action_id"));

        ActionBean actionBean = dataAccesser.getOneAction(actionId);
        RuleBean ruleBean = dataAccesser.getOneRule(actionId);
        List<ClassificationBean> classList = dataAccesser.getAllClassification();

        Map<String, String> graphInfoMap = graphJsonInfoParse(actionBean.getGraph_info());
        Map<String, String> ruleColsMap = graphJsonInfoParse(ruleBean.getCols());

        model.addAttribute("graphInfoMap", graphInfoMap);
        model.addAttribute("ruleColsMap", ruleColsMap);
        model.addAttribute("classList", classList);
        model.addAttribute("actionBean", actionBean);
        model.addAttribute("ruleBean", ruleBean);

        return "reviseGraph";
    }

    @RequestMapping("/test.shtml")
    public
    @ResponseBody
    String test(@RequestParam(value = "id", required = false, defaultValue = "World") String[] name, HttpServletRequest request, Model model, ModelAndView modelAndView) {

//        dataAccesser.getAllActions();
//        logger.info("[------controller------]   : getAllActions--after");
//        System.out.println("------" + request.getParameter("jsonData"));
        String str = request.getParameter("jsonData");
        ObjectMapper mapper = new ObjectMapper();
        try {
            JsonNode root = mapper.readTree(str);
            // 提取 data
//            JsonNode data = root.path("data");
            System.out.println("------" + root.get("data").asText());
            System.out.println("------" + root.get("info").asText());
            // 提取 info
//            JsonNode info = data.path("info");

//            System.out.println(info.size());

//            // 得到 info 的第 0 个
//            JsonNode item = info.get(0);
//            System.out.println(item.get("id"));
//            System.out.println(item.get("timestamp"));

//            // 得到 info 的第 2 个
//            item = info.get(2);
//            System.out.println(item.get("id"));
//            System.out.println(item.get("timestamp"));

            // 遍历 info 内的 array
//            if (info.isArray())
//            {
//                for (JsonNode objNode : info)
//                {
//                    System.out.println(objNode);
//                }
//            }
        } catch (IOException e) {
            logger.info("[------Controller------]: test IOException");
            e.printStackTrace();
        }
        return "test";
    }

    /**
     * 获取每个图表相关信息，用于展示
     *
     * @param actionBean
     * @return GraphBean
     */
    public GraphBean getGraphBean(ActionBean actionBean) {

        String queryResultJsonStr = dataAccesser.queryResultStr(actionBean);
        GraphObject graphObject = new GraphObject(actionBean, queryResultJsonStr);

        GraphBean graphBean = new GraphBean();

        graphBean.setName(actionBean.getAction_name());
        graphBean.setId(actionBean.getAction_id());
        graphBean.setType(actionBean.getGraph_type());
        graphBean.setNotes(actionBean.getNotes());
        graphBean.setJsonNode(graphObject.getGraphData());

        return graphBean;
    }

    /**
     * 获取前端传来的 ActionBean,RuleBean
     *
     * @param request
     * @return
     */
    public List getActionAndRuleBean(HttpServletRequest request) {
        List beanList = new ArrayList<>();
        ActionBean actionBean = new ActionBean();
        RuleBean ruleBean = new RuleBean();
        if (request.getParameter("action_id") != null) {
            actionBean.setAction_id(Integer.parseInt(request.getParameter("action_id")));
            ruleBean.setAction_id(Integer.parseInt(request.getParameter("action_id")));
        }
        actionBean.setAction_name(request.getParameter("action_name"));
        actionBean.setClassification_id(Integer.parseInt(request.getParameter("classification_id")));
        actionBean.setNotes(request.getParameter("notes"));
        actionBean.setGraph_type(request.getParameter("graph_type"));
        actionBean.setGraph_info(request.getParameter("graph_info"));
        actionBean.setExec_type(request.getParameter("exec_type"));
        actionBean.setInteral_time(Integer.parseInt(request.getParameter("interal_time")));
        logger.info("[------Controller  ActionBean------]: Complete" + request.getParameter("graph_type"));

        ruleBean.setRule_value(request.getParameter("rule_value"));
        ruleBean.setHbase_table_name(request.getParameter("hbase_table_name"));
        ruleBean.setTime_type(request.getParameter("time_type"));
        ruleBean.setInterval_time(request.getParameter("interval_time"));
        ruleBean.setCols(request.getParameter("cols"));
        logger.info("[------Controller  RuleBean------]:"+request.getParameter("cols"));
        logger.info("[------Controller  RuleBean------]: Complete");

        beanList.add(actionBean);
        beanList.add(ruleBean);

        return beanList;
    }

    /**
     * 将json串转存为Map
     * @param jsonStr
     * @return
     */
    public Map<String, String> graphJsonInfoParse(String jsonStr) {
        Map<String, String> map = new HashMap<String, String>();
        ObjectMapper mapper = new ObjectMapper();
        try {
            // convert JSON string to Map
            map = mapper.readValue(jsonStr, new TypeReference<Map<String, String>>(){});

//            logger.info("[------Controller jsonMap------]: "+map);
//            JsonNode node =  mapper.readTree(jsonStr);
//            list.add(node.get("time_key").asText());
//            list.add(node.get("x_line").asText());
//            list.add(node.get("groups_by").asText());
//            list.add(node.get("value_col").asText());
//            list.add(node.get("need_to_show_as_chinese").asText());
        } catch (IOException e) {
            logger.info("[------Controller------]: graphJsonInfoParse IOException");
            e.printStackTrace();
        }
        return map;
    }

    //    @RequestMapping("/testaction.shtml")
//    @ResponseBody
//    public ModelAndView testwidget(HttpServletRequest request, Model model, ModelAndView modelAndView) {
////        @RequestParam(value = "datas[]") String[] datas
//        List<GraphBean> graphBeanList = new ArrayList<GraphBean>();
//        ActionBean actionBean = dataAccesser.getOneAction(request.getParameter("id"));
//        logger.info("[------controller------]: actionBean-ID" + request.getParameter("id"));
//
//        String queryResultJsonStr = queryResultStr(actionBean);
//        GraphObject graphObject = new GraphObject(actionBean,queryResultJsonStr);
//        GraphBean graphBean = new GraphBean();
//
//        graphBean.setName(actionBean.getAction_name());
//        graphBean.setId(actionBean.getAction_id());
//        graphBean.setType(actionBean.getGraph_type());
//
//        graphBean.setJsonNode(graphObject.getGraphData());
//
//        graphBeanList.add(graphBean);
//
//        model.addAttribute("beanList", graphBeanList);
//
//        logger.info("[------controller------]: action-controller");
//        modelAndView.setViewName("actionWidget");
//        return modelAndView;
//    }
}
